package wang.encoding.mroot.model.entity.system

import com.baomidou.mybatisplus.activerecord.Model
import com.baomidou.mybatisplus.annotations.TableField
import com.baomidou.mybatisplus.annotations.TableId
import com.baomidou.mybatisplus.annotations.TableName
import com.baomidou.mybatisplus.enums.IdType
import org.apache.commons.collections.CollectionUtils
import org.hibernate.validator.constraints.Range
import java.io.Serializable
import java.math.BigInteger
import java.util.*
import javax.validation.constraints.NotNull
import javax.validation.constraints.Past
import javax.validation.constraints.Pattern

/**
 *
 * 权限表实体类
 *
 * @author ErYang
 *
 */
@TableName("system_rule")
class Rule : Model<Rule>(), Serializable, Comparable<Rule> {

    companion object {

        private const val serialVersionUID = -4580936849718430128L

        /* 属性名称常量开始 */

        // -------------------------------------------------------------------------------------------------

        const val ID: String = "id"

        const val TITLE: String = "title"

        const val NAME: String = "name"

        const val URL: String = "url"


        // -------------------------------------------------------------------------------------------------

        /* 属性名称常量结束 */

        /**
         * 现有的对象赋值给一个新的对象
         *
         * @param rule  Rule
         * @return Rule
         */
        fun copy2New(rule: Rule): Rule {
            val newRule = Rule()
            newRule.id = rule.id
            newRule.type = rule.type
            newRule.title = rule.title
            newRule.name = rule.name
            newRule.url = rule.url
            newRule.pid = rule.pid
            newRule.sort = rule.sort
            newRule.status = rule.status
            newRule.remark = rule.remark
            newRule.gmtCreate = rule.gmtCreate
            newRule.gmtCreateIp = rule.gmtCreateIp
            newRule.gmtModified = rule.gmtModified
            return newRule
        }

        // -------------------------------------------------------------------------------------------------

        /**
         * list 转为 tree list
         *
         * @param list list
         * @return tree list
         */
        fun list2Tree(list: List<Rule>?): List<Rule>? {
            if (null == list) {
                return null
            }
            val roots: List<Rule> = listRoot(list)
            val notRoots: List<*> = CollectionUtils.subtract(list, roots) as List<*>
            for (root: Rule in roots) {
                @Suppress("UNCHECKED_CAST")
                root.childrenList = listChildren(root, notRoots as List<Rule>)
            }
            return roots
        }

        // -------------------------------------------------------------------------------------------------

        /**
         * 找到根节点
         *
         * @param allNodes allNodes
         * @return list 集合
         */
        private fun listRoot(allNodes: List<Rule>): List<Rule> {
            val results = ArrayList<Rule>()
            for (node: Rule in allNodes) {
                val isRoot: Boolean = allNodes.none { node.pid == it.id }
                if (isRoot) {
                    results.add(node)
                }
            }
            return results
        }

        // -------------------------------------------------------------------------------------------------

        /**
         * 根据根节点找到子节点
         *
         * @param root     root
         * @param allNodes allNodes
         * @return list 集合
         */
        private fun listChildren(root: Rule,
                                 allNodes: List<Rule>): List<Rule> {
            val children = ArrayList<Rule>()
            for (comparedOne: Rule in allNodes) {
                if (comparedOne.pid == root.id) {
                    comparedOne.parentRule = root
                    children.add(comparedOne)
                }
            }
            if (allNodes.isNotEmpty()) {
                val notChildren: List<*> = CollectionUtils.subtract(allNodes, children) as List<*>
                for (child: Rule in children) {
                    @Suppress("UNCHECKED_CAST")
                    val tmpChildren: List<Rule> = listChildren(child, notChildren as List<Rule>)
                    child.childrenList = tmpChildren
                }
            }
            return children
        }

        // -------------------------------------------------------------------------------------------------

    }

    // -------------------------------------------------------------------------------------------------

    /**
     * 权限id
     */
    @TableId(value = "id", type = IdType.AUTO)
    var id: BigInteger? = null
    /**
     * 父级权限
     */
    @NotNull(message = "validation.system.rule.pid.pattern")
    @Range(min = 0, message = "validation.system.rule.pid.pattern")
    var pid: BigInteger? = null
    /**
     * 1-url地址,2-主菜单;3-子级菜单,4-按钮
     */
    @NotNull(message = "validation.type.range")
    @Range(min = 1, max = 4, message = "validation.type.range")
    var type: Int? = null
    /**
     * 标识
     */
    @Pattern(regexp = "^[a-zA-Z0-9_\\u4e00-\\u9fa5]{2,80}$", message = "validation.name.pattern")
    var name: String? = null
    /**
     * 名称
     */
    @Pattern(regexp = "^[a-zA-Z0-9_\\u4e00-\\u9fa5]{2,80}$", message = "validation.title.pattern")
    var title: String? = null
    /**
     * url地址
     */
    @Pattern(regexp = "^[a-zA-Z0-9/]{1,255}$", message = "validation.system.rule.url.pattern")
    var url: String? = null
    /**
     * 排序
     */
    @Range(min = 0, message = "validation.sort.range")
    var sort: Int? = null
    /**
     * 状态（-1：已删除，0：禁用，1：正常）
     */
    @NotNull(message = "validation.status.range")
    @Range(min = 1, max = 3, message = "validation.status.range")
    var status: Int? = null
    /**
     * 备注
     */
    @Pattern(regexp = "^[a-zA-Z0-9，。、\\u4e00-\\u9fa5]{0,200}$", message = "validation.remark.pattern")
    var remark: String? = null
    /**
     * 添加时间
     */
    @TableField("gmt_create")
    @Past(message = "validation.gmtCreate.past")
    var gmtCreate: Date? = null
    /**
     * 添加ip
     */
    @TableField("gmt_create_ip")
    @Pattern(regexp = "^[0-9.]{6,50}\$", message = "validation.gmtCreateIp.pattern")
    var gmtCreateIp: String? = null
    /**
     * 更新时间
     */
    @TableField("gmt_modified")
    @Past(message = "validation.gmtModified.past")
    var gmtModified: Date? = null

    /**
     * 父级权限
     */
    @TableField(exist = false)
    var parentRule: Rule? = null
    /**
     * 子级权限
     */
    @TableField(exist = false)
    var childrenList: List<Rule>? = null

    // -------------------------------------------------------------------------------------------------

    override fun pkVal(): Serializable? {
        return this.id
    }

    // -------------------------------------------------------------------------------------------------

    /**
     * 排序规则
     */
    override fun compareTo(other: Rule): Int {
        return when {
        // 正整数是大于
            this.id!! > other.id ->
                1
        //负整数是小于
            this.id!! < other.id ->
                -1
        // 0为等于
            else ->
                0
        }
    }

    // -------------------------------------------------------------------------------------------------

    override fun equals(other: Any?): Boolean {
        if (this === other) return true
        if (javaClass != other?.javaClass) return false

        other as Rule

        if (id != other.id) return false
        if (pid != other.pid) return false
        if (type != other.type) return false
        if (name != other.name) return false
        if (title != other.title) return false
        if (url != other.url) return false
        if (sort != other.sort) return false
        if (status != other.status) return false
        if (remark != other.remark) return false
        if (gmtCreate != other.gmtCreate) return false
        if (gmtCreateIp != other.gmtCreateIp) return false
        if (gmtModified != other.gmtModified) return false
        if (parentRule != other.parentRule) return false
        if (childrenList != other.childrenList) return false

        return true
    }

    override fun hashCode(): Int {
        var result = id?.hashCode() ?: 0
        result = 31 * result + (pid?.hashCode() ?: 0)
        result = 31 * result + (type ?: 0)
        result = 31 * result + (name?.hashCode() ?: 0)
        result = 31 * result + (title?.hashCode() ?: 0)
        result = 31 * result + (url?.hashCode() ?: 0)
        result = 31 * result + (sort ?: 0)
        result = 31 * result + (status ?: 0)
        result = 31 * result + (remark?.hashCode() ?: 0)
        result = 31 * result + (gmtCreate?.hashCode() ?: 0)
        result = 31 * result + (gmtCreateIp?.hashCode() ?: 0)
        result = 31 * result + (gmtModified?.hashCode() ?: 0)
        result = 31 * result + (parentRule?.hashCode() ?: 0)
        result = 31 * result + (childrenList?.hashCode() ?: 0)
        return result
    }

    override fun toString(): String {
        return "Rule(id=$id, pid=$pid, type=$type, name=$name, title=$title, url=$url, sort=$sort, status=$status, remark=$remark, gmtCreate=$gmtCreate, gmtCreateIp=$gmtCreateIp, gmtModified=$gmtModified, parentRule=$parentRule, childrenList=$childrenList)"
    }

    // -------------------------------------------------------------------------------------------------

}

// -----------------------------------------------------------------------------------------------------

// End Rule class

/* End of file Rule.kt */
/* Location: ./src/main/kotlin/wang/encoding/mroot/model/entity/system/Rule.kt */

// -----------------------------------------------------------------------------------------------------
// +----------------------------------------------------------------------------------------------------
// |                           ErYang出品 属于小极品  O(∩_∩)O~~   共同学习    共同进步
// +----------------------------------------------------------------------------------------------------
// -----------------------------------------------------------------------------------------------------
